package com.wskeee.ec.components
{
	import com.wskeee.ec.ens;
	import com.wskeee.ec.components.skin.ButtonSkin;
	import com.wskeee.ec.core.SkinableComponent;
	import com.wskeee.ec.styles.StyleNames;
	
	import flash.events.Event;
	import flash.events.MouseEvent;
	
	use namespace ens;
	
	[Event(name="change", type="flash.events.Event")]
	
	public class Button extends SkinableComponent
	{
		public static const BUTTON_STATE_UP:String = "up";
		public static const BUTTON_STATE_OVER:String = "over";
		public static const BUTTON_STATE_DOWN:String = "down";
		
		protected var _iconData:Object;
		protected var _labelData:String = "Button";
		
		protected var _state:String = "up";
		protected var _toggle:Boolean = false;
		protected var _selected:Boolean = false;
		
		protected var stateChangedFlag:Boolean = false;
		protected var labelChangedFlag:Boolean = false;
		protected var iconChangedFlag:Boolean = false;
		
		protected var _labelPlacement:String = "right";
		
		public function Button()
		{
			super();
			height = 20;
			buttonMode = true;
		}
		
		//========================= override ====================
		//---------------------
		//EComponent
		//---------------------

		override protected function initialize():void
		{
			super.initialize();
			initMouseEvent();
		}
		override protected function initChildren():void
		{
			super.initChildren();
			mouseChildren = false;
		}
		
		//---------------------
		//skinable style 
		//---------------------
		override protected function initStyle():void
		{
			super.initStyle();
			styles[StyleNames.TEXT_PADDING] = 5;
		}
		
		override public function destory():void
		{
			destoryMouseEvent();
			super.destory();
		}
		//========================= end =========================
		
		//========================= mouseEvent ==================
		protected function initMouseEvent():void
		{
			addEventListener(MouseEvent.MOUSE_DOWN,onMouseDown);
			addEventListener(MouseEvent.ROLL_OVER,onRollOver);
			addEventListener(MouseEvent.ROLL_OUT,onRollOut);
		}
		
		protected function onRollOut(event:MouseEvent):void
		{
			if(_state == BUTTON_STATE_OVER)
				changeState(BUTTON_STATE_UP);
		}
		
		protected function onRollOver(event:MouseEvent):void
		{
			if(_state == BUTTON_STATE_UP)
				changeState(BUTTON_STATE_OVER);
		}
		
		protected function onMouseDown(event:MouseEvent):void
		{
			stage.addEventListener(MouseEvent.MOUSE_UP,onStageMouseUp);
			changeState(BUTTON_STATE_DOWN);
		}
		
		protected function onStageMouseUp(event:MouseEvent):void
		{
			stage.removeEventListener(MouseEvent.MOUSE_UP,onStageMouseUp);
			onButtonMouseUp();
		}
		
		protected function destoryMouseEvent():void
		{
			removeEventListener(MouseEvent.MOUSE_DOWN,onMouseDown);
			removeEventListener(MouseEvent.ROLL_OVER,onRollOver);
			if(stage)
				stage.removeEventListener(MouseEvent.MOUSE_UP,onStageMouseUp);
		}
		//========================= end =========================
		
		//========================= utils =======================
		protected function onButtonMouseUp():void
		{
			if(toggle)
				selected = !_selected;
			
			if(!toggle || !_selected)
				changeState(BUTTON_STATE_UP);
		}
		protected function changeState(s:String):void
		{
			_state = s;
			stateChangedFlag = true;
			invalidateProperties();
		}
		//========================= end =========================
		
		//========================= validate ====================
		override protected function commitProperties():void
		{
			super.commitProperties();
			if(stateChangedFlag || iconChangedFlag || labelChangedFlag)
			{
				stateChangedFlag = iconChangedFlag = labelChangedFlag = false;
				invalidateSize();
			}
		}
		//========================= end =========================
		
		//========================= att ========================
		/**
		 * 设置按钮 icon 
		 * @return 
		 * 
		 */
		public function get icon():Object
		{
			return _iconData;
		}
		
		public function set icon(value:Object):void
		{
			_iconData = value;
			iconChangedFlag = true;
			invalidateProperties();
		}
		
		/**
		 * 设置按钮显示的文字 
		 * @return 
		 * 
		 */
		public function get label():String
		{
			return _labelData;
		}
		
		public function set label(value:String):void
		{
			_labelData = value;
			labelChangedFlag = true;
			invalidateProperties();
		}
		
		/**
		 * 按钮现在的状态,up、over、down 
		 * @return 
		 * 
		 */
		public function get state():String
		{
			return _state;
		}
		
		public function set toggle(bo:Boolean):void
		{
			_toggle = bo;
		}
		
		public function get toggle():Boolean
		{
			return _toggle;
		}
		
		public function get selected():Boolean
		{
			return _selected;
		}
		
		public function set selected(bo:Boolean):void
		{
			if(_selected!=bo)
			{
				_selected = bo;
				changeState(bo ? BUTTON_STATE_DOWN : BUTTON_STATE_UP);
				dispatchEvent(new Event(Event.CHANGE));
			}
		}
		
		/**
		 * 标签相对于指定图标的位置。 
		 * @return LayoutCost.LEFT or LayoutCost.RIGHT
		 * 
		 */
		public function get labelPlacement():String
		{
			return _labelPlacement;
		}
		
		public function set labelPlacement(value:String):void
		{
			_labelPlacement = value;
		}
		
		//---------------------
		//style skin
		//---------------------
		public function get upSkin():Object
		{
			return getStyle("upSkin");
		}
		
		public function set upSkin(value:Object):void
		{
			if(upSkin!=value)
				setStyle("upSkin",value);
		}
		
		public function get overSkin():Object
		{
			return getStyle("upSkin");
		}
		
		public function set overSkin(value:Object):void
		{
			if(overSkin!=value)
				setStyle("overSkin",value);
		}
		
		public function get downSkin():Object
		{
			return getStyle("downSkin");
		}
		
		public function set downSkin(value:Object):void
		{
			if(downSkin!=value)
				setStyle("downSkin",value);
		}
		
		
		//---------------------
		//override ecomponent
		//---------------------
		override public function set enabled(bo:Boolean):void
		{
			super.enabled = bo;
			mouseChildren = false;
		}
		
		//---------------------
		//skin
		//---------------------
		override public function get DefaultSkinDrawer():Class
		{
			return ButtonSkin;
		}
		//========================= end =========================
	}
}